import multiprocessing
import os
import signal
from django.shortcuts import render, redirect

import AppManager.Mysql
import HostManager.SSH
from AppMonitor import ZabbixApi
import re
import time
from OpManager import settings
from Logs import views as Logs_views

Cpu_Mem = multiprocessing.Manager().list(range(1))
CM_time = multiprocessing.Manager().list(range(1))
Cpu_Mem[0] = ''
CM_time[0] = ''
ZabbixProblems = multiprocessing.Manager().list(range(1))
ZabbixProblems[0] = ''
OpMonitor = multiprocessing.Manager().list(range(1))
OpMonitor[0] = 0


# 去获取需要在后台跑的函数
def forkget():
    Logs_views.log("开始后台循环获取监控数据")
    forkget_zabbix()
    forkget_CpuMem()


# 重复跑需要跑的函数
def startfork():
    i = 0
    while True:
        forkget()
        i += 1
        print("第" + str(i) + "次监控数据")
        time.sleep(60 * 5)


def disk2int(string):
    return round(int(string) / 1024 / 1024, 2)


def netstatList(netstat):
    res = {}
    netstat_list = netstat.split("\n")
    i = 1
    for port in netstat_list:
        port = port.split()
        if len(port):
            res[str(i)] = port
            i += 1
    return res


def forkget_CpuMem():
    global Cpu_Mem, CM_time
    # print("先获取一下CPU_MEM的数据：")
    # print(Cpu_Mem[0])
    result = {}
    CM_hostlist = AppManager.Mysql.MysqlPool("SELECT * FROM `host`", 99)
    # print("受监控的主机：", CM_hostlist)
    for CM_host in CM_hostlist:
        print("获取系统监控数据：", CM_host["hostname"])
        try:
            result[CM_host["hostname"]] = {"CPU": {}, "Mem": {}}
            CM_host_dev_sql = "SELECT * FROM `host_dev` WHERE hostname LIKE '{0}'".format(CM_host["hostname"])
            hostdev = AppManager.Mysql.MysqlPool(CM_host_dev_sql, 1)

            cpu_all = "top -bn1 |grep Cpu > /tmp/cpu_top && sed -i 's/\([a-z]\|\ \|%\|C\|(\|)\|:\)//g' /tmp/cpu_top"
            cpu_us = "cat /tmp/cpu_top | awk -F\",\" '{print $1}'"
            cpu_sy = "cat /tmp/cpu_top | awk -F\",\" '{print $2}'"
            cpu_ni = "cat /tmp/cpu_top | awk -F\",\" '{print $3}'"
            cpu_free = "cat /tmp/cpu_top | awk -F\",\" '{print $4}'"

            Mem_all = "free -m | grep Mem > /tmp/free_Mem"
            Mem_total = "cat /tmp/free_Mem |awk '{print $2}'"
            Mem_used = "cat /tmp/free_Mem |awk '{print $3}'"

            disk_all = 'df > /tmp/disk_all'
            # 获取 root 大小
            disk_root_Size = 'cat /tmp/disk_all | grep -E "/$" | awk \'{print $2}\''
            disk_root_Avail = 'cat /tmp/disk_all | grep -E "/$" | awk \'{print $4}\''
            # 获取 boot 大小
            disk_boot_Size = 'cat /tmp/disk_all | grep -E "/boot$" | awk \'{print $2}\''
            disk_boot_Avail = 'cat /tmp/disk_all | grep -E "/boot$" | awk \'{print $4}\''
            # 获取 home 大小
            disk_home_Size = 'cat /tmp/disk_all | grep -E "/home$" | awk \'{print $2}\''
            disk_home_Avail = 'cat /tmp/disk_all | grep -E "/home$" | awk \'{print $4}\''

            netstat_lntp = 'netstat -lntp > /tmp/netstat && sed -i \'1,2d\' /tmp/netstat && cat /tmp/netstat'

            commonds = [cpu_all, cpu_us, cpu_sy, cpu_ni, cpu_free, Mem_all, Mem_total, Mem_used, disk_all,
                        disk_root_Size, disk_root_Avail,
                        disk_boot_Size, disk_boot_Avail,
                        disk_home_Size, disk_home_Avail,
                        netstat_lntp
                        ]
            # print("0")
            res = HostManager.SSH.SshComm(CM_host["ip"], CM_host["ssh_port"], hostdev["Suser"], hostdev["Spasswd"], commonds)
            # print("1")
            # print(res)
            result[CM_host["hostname"]]["CPU"] = {
                "cpu_us": str2float(res[cpu_us]["stdout"]),
                "cpu_sy": str2float(res[cpu_sy]["stdout"]),
                "cpu_ni": str2float(res[cpu_ni]["stdout"]),
                "cpu_free": str2float(res[cpu_free]["stdout"])
            }
            # print("2")
            result[CM_host["hostname"]]["Mem"] = {
                "Mem_free": int(res[Mem_total]["stdout"]) - int(res[Mem_used]["stdout"]),
                "Mem_used": int(res[Mem_used]["stdout"])}
            # print("3")
            if res[disk_home_Size]["stdout"] == "":
                res[disk_home_Size]["stdout"] = "0"
                res[disk_home_Avail]["stdout"] = "0"

            result[CM_host["hostname"]]["Disk"] = {
                "disk_root_Size": disk2int(res[disk_root_Size]["stdout"]),
                "disk_root_Avail": disk2int(res[disk_root_Avail]["stdout"]),
                "disk_root_Use": disk2int(int(res[disk_root_Size]["stdout"]) - int(res[disk_root_Avail]["stdout"])),
                "disk_boot_Size": disk2int(res[disk_boot_Size]["stdout"]),
                "disk_boot_Avail": disk2int(res[disk_boot_Avail]["stdout"]),
                "disk_boot_Use": disk2int(int(res[disk_boot_Size]["stdout"]) - int(res[disk_boot_Avail]["stdout"])),
                "disk_home_Size": disk2int(res[disk_home_Size]["stdout"]),
                "disk_home_Avail": disk2int(res[disk_home_Avail]["stdout"]),
                "disk_home_Use": disk2int(int(res[disk_home_Size]["stdout"]) - int(res[disk_home_Avail]["stdout"])),
            }
            # print("4")
            result[CM_host["hostname"]]["Port"] = netstatList(res[netstat_lntp]["stdout"])
            result[CM_host["hostname"]]["ID"] = CM_host["id"]

        except Exception as e:
            print("\nERROR")
            print("AppMonitor_Views出现错误", type(e), e)
            print("ERROR\n")
            result[CM_host["hostname"]]["CPU"] = {"cpu_us": "获取错误"}
    now = time.strftime('%Y/%m/%d %H:%M:%S', time.localtime(time.time()))
    # print(result)
    # print(type(result))
    Cpu_Mem[0] = result
    # print(Cpu_Mem[0])
    CM_time[0] = now
    Logs_views.log("Cpu_Mem:" + str(Cpu_Mem))


def str2float(string):
    if string:
        res = re.findall("([0-9].*[0-9])", string)[0]
        res = float(res)
        return res


# 系统监控的页面展示
@settings.auth(AuthType="AppMonitor", AuthNum=1)
def linuxpage(requests):
    # print(result)
    # print(CM_time[0])
    result = Cpu_Mem[0]
    context = {
        "host_len": len(result),
        "result": result,
        "CM_time": CM_time[0]
    }
    return render(requests, 'LinuxMonitor.html', context)


def refresh(requests):
    forkget()
    res = redirect('/monitor_linux')
    return res


def refreshzabbix(requests):
    forkget_zabbix()
    res = redirect('/monitor_zabbix')
    return res


def forkget_zabbix():
    global ZabbixProblems
    ZabbixProblems[0] = ZabbixApi.getProblems()
    Logs_views.log("ZabbixProblem:" + str(ZabbixProblems[0]))


# Zabbix监控的页面展示
@settings.auth(AuthType="AppMonitor", AuthNum=2)
def zabbixpage(requests):
    context = {
        "ZabbixProblemPage": ZabbixApi.zabbix_url + "/zabbix.php?action=problem.view",
        "ProblmeList": ZabbixProblems[0]
    }
    return render(requests, 'ZabbixMonitor.html', context)


def fork_Op(Pids: list):
    global OpMonitor
    i = 0
    try:
        while True:
            OpMonitor[0] = i
            i += 2
            time.sleep(2)
    except BrokenPipeError:
        print("子进程全部退出")
        Pids.append(os.getpid())
        for pid in Pids:
            print("子进程", pid)
            os.kill(pid, signal.SIGKILL)


p = multiprocessing.Process(target=startfork, args=())
p.start()
settings.PIDs.append(p.pid)
Logs_views.log("创建获取监控数据的子进程：" + str(p.pid))
